//
//  PSFilterSecondPlusKingTrick.m
//  PrefCore
//
//  Created by Sergey on 6/20/14.
//  Copyright (c) 2014 Play-on-smart. All rights reserved.
//

#import "PSFilter.h"

PSHandHash PSFilterSecondPlusKingTrick(
    PSHandHash candidates
,   PSPlayerId player
,   PSHandHash playerCards
,   PSPlayerId declarer
,   PSHandHash declarerCards
) {
    PSCardSuit suits[PS_CARD_SUIT_RISING_LEN] = {0};
    size_t size = 0;
    // Determine if declarer has second plus king
    for (int i = 0 ; i != PS_CARD_SUIT_RISING_LEN ; i++) {
        PSCardSuit s = PSCardSuitRising[i];
        if (PSHandKeepSuit(candidates, s) != 0) {
            PSCardRankSet cards = PSHandGetSuit(declarerCards, s);
            int length = PSCardSetSize(cards);
            // "Second king plus" is defined as 2-3 cards long suit with no ace, with a king
            // but without marriage or triliage. Marriage with a cover is also considered.
            if (!PSCardSetContainsCard(cards, kMaskAce)
            && PSCardSetContainsCard(cards, kMaskKing)
            && ((length == 2 && !PSCardSetContainsCard(cards, kMaskQueen)) ||
                (length == 3 && (!PSCardSetContainsCard(cards, kMaskQueen) ||
                                 !PSCardSetContainsCard(cards, kMaskJack))))) {
                suits[size++] = s;
            }
        }
    }
    // If there is no second plus king in any suit, return all candidates:
    if (size == 0) {
        return candidates;
    }
    // The declarer's hand is next
    if (PSGameNextPlayerId(player) == declarer) {
        for (int i = 0; i < size; i++) {
            PSCardRankSet cards = PSHandGetSuit(playerCards, suits[i]);    
            // If the player's hand is 0 and declarer is 1 and player has no ace, then
            // all candidates in this suit are valid, because the partner has the ace:
            if (!PSCardSetContainsCard(cards, kMaskAce)) {
                suits[i] = kSuitNone;
            }
        }
    }
    int res = candidates;
    // All remaining suit sets should be removed from candidates,
    // because they can make the second plus king to take a trick:
    for (int i = 0 ; i < size ; i++) {
        PSCardSuit s = suits[i];
        if (s != kSuitNone) {
            res = PSHandRemoveSuit(res, s);
        }
    }
    return res != 0 ? res : candidates;

}